home *** CD-ROM | disk | FTP | other *** search
/ Chip 2007 January, February, March & April / Chip-Cover-CD-2007-02.iso / Pakiet bezpieczenstwa / mini Pentoo LiveCD 2006.1 / mpentoo-2006.1.iso / livecd.squashfs / usr / include / linux / wait.h < prev    next >
C/C++ Source or Header  |  2005-10-13  |  12KB  |  406 lines

  1. #ifndef _LINUX_WAIT_H
  2. #define _LINUX_WAIT_H
  3.  
  4. #define WNOHANG        0x00000001
  5. #define WUNTRACED    0x00000002
  6. #define WSTOPPED    WUNTRACED
  7. #define WEXITED        0x00000004
  8. #define WCONTINUED    0x00000008
  9. #define WNOWAIT        0x01000000    /* Don't reap, just poll status.  */
  10.  
  11. #define __WNOTHREAD    0x20000000    /* Don't wait on children of other threads in this group */
  12. #define __WALL        0x40000000    /* Wait on all children, regardless of type */
  13. #define __WCLONE    0x80000000    /* Wait only on non-SIGCHLD children */
  14.  
  15. /* First argument to waitid: */
  16. #define P_ALL        0
  17. #define P_PID        1
  18. #define P_PGID        2
  19.  
  20. #include <linux/config.h>
  21. #include <linux/list.h>
  22. #include <linux/stddef.h>
  23. #include <linux/spinlock.h>
  24. #include <asm/system.h>
  25. #include <asm/current.h>
  26.  
  27. typedef struct __wait_queue wait_queue_t;
  28. typedef int (*wait_queue_func_t)(wait_queue_t *wait, unsigned mode, int sync, void *key);
  29. int default_wake_function(wait_queue_t *wait, unsigned mode, int sync, void *key);
  30.  
  31. struct __wait_queue {
  32.     unsigned int flags;
  33. #define WQ_FLAG_EXCLUSIVE    0x01
  34.     struct task_struct * task;
  35.     wait_queue_func_t func;
  36.     struct list_head task_list;
  37. };
  38.  
  39. struct wait_bit_key {
  40.     void *flags;
  41.     int bit_nr;
  42. };
  43.  
  44. struct wait_bit_queue {
  45.     struct wait_bit_key key;
  46.     wait_queue_t wait;
  47. };
  48.  
  49. struct __wait_queue_head {
  50.     spinlock_t lock;
  51.     struct list_head task_list;
  52. };
  53. typedef struct __wait_queue_head wait_queue_head_t;
  54.  
  55. #include <linux/pid.h>
  56.  
  57. /*
  58.  * Macros for declaration and initialisaton of the datatypes
  59.  */
  60.  
  61. #define __WAITQUEUE_INITIALIZER(name, tsk) {                \
  62.     .task        = tsk,                        \
  63.     .func        = default_wake_function,            \
  64.     .task_list    = { NULL, NULL } }
  65.  
  66. #define DECLARE_WAITQUEUE(name, tsk)                    \
  67.     wait_queue_t name = __WAITQUEUE_INITIALIZER(name, tsk)
  68.  
  69. #define __WAIT_QUEUE_HEAD_INITIALIZER(name) {                \
  70.     .lock        = SPIN_LOCK_UNLOCKED,                \
  71.     .task_list    = { &(name).task_list, &(name).task_list } }
  72.  
  73. #define DECLARE_WAIT_QUEUE_HEAD(name) \
  74.     wait_queue_head_t name = __WAIT_QUEUE_HEAD_INITIALIZER(name)
  75.  
  76. #define __WAIT_BIT_KEY_INITIALIZER(word, bit)                \
  77.     { .flags = word, .bit_nr = bit, }
  78.  
  79. static inline void init_waitqueue_head(wait_queue_head_t *q)
  80. {
  81.     q->lock = SPIN_LOCK_UNLOCKED;
  82.     INIT_LIST_HEAD(&q->task_list);
  83. }
  84.  
  85. static inline void init_waitqueue_entry(wait_queue_t *q, struct task_struct *p)
  86. {
  87.     q->flags = 0;
  88.     q->task = p;
  89.     q->func = default_wake_function;
  90. }
  91.  
  92. static inline void init_waitqueue_func_entry(wait_queue_t *q,
  93.                     wait_queue_func_t func)
  94. {
  95.     q->flags = 0;
  96.     q->task = NULL;
  97.     q->func = func;
  98. }
  99.  
  100. static inline int waitqueue_active(wait_queue_head_t *q)
  101. {
  102.     return !list_empty(&q->task_list);
  103. }
  104.  
  105. /*
  106.  * Used to distinguish between sync and async io wait context:
  107.  * sync i/o typically specifies a NULL wait queue entry or a wait
  108.  * queue entry bound to a task (current task) to wake up.
  109.  * aio specifies a wait queue entry with an async notification
  110.  * callback routine, not associated with any task.
  111.  */
  112. #define is_sync_wait(wait)    (!(wait) || ((wait)->task))
  113.  
  114. extern void FASTCALL(add_wait_queue(wait_queue_head_t *q, wait_queue_t * wait));
  115. extern void FASTCALL(add_wait_queue_exclusive(wait_queue_head_t *q, wait_queue_t * wait));
  116. extern void FASTCALL(remove_wait_queue(wait_queue_head_t *q, wait_queue_t * wait));
  117.  
  118. #ifdef __KERNEL__
  119.  
  120. static inline void __add_wait_queue(wait_queue_head_t *head, wait_queue_t *new)
  121. {
  122.     list_add(&new->task_list, &head->task_list);
  123. }
  124.  
  125. /*
  126.  * Used for wake-one threads:
  127.  */
  128. static inline void __add_wait_queue_tail(wait_queue_head_t *head,
  129.                         wait_queue_t *new)
  130. {
  131.     list_add_tail(&new->task_list, &head->task_list);
  132. }
  133.  
  134. static inline void __remove_wait_queue(wait_queue_head_t *head,
  135.                             wait_queue_t *old)
  136. {
  137.     list_del(&old->task_list);
  138. }
  139.  
  140. #endif /* __KERNEL__ */
  141.  
  142. void FASTCALL(__wake_up(wait_queue_head_t *q, unsigned int mode, int nr, void *key));
  143. extern void FASTCALL(__wake_up_locked(wait_queue_head_t *q, unsigned int mode));
  144. extern void FASTCALL(__wake_up_sync(wait_queue_head_t *q, unsigned int mode, int nr));
  145. void FASTCALL(__wake_up_bit(wait_queue_head_t *, void *, int));
  146. int FASTCALL(__wait_on_bit(wait_queue_head_t *, struct wait_bit_queue *, int (*)(void *), unsigned));
  147. int FASTCALL(__wait_on_bit_lock(wait_queue_head_t *, struct wait_bit_queue *, int (*)(void *), unsigned));
  148. void FASTCALL(wake_up_bit(void *, int));
  149. int FASTCALL(out_of_line_wait_on_bit(void *, int, int (*)(void *), unsigned));
  150. int FASTCALL(out_of_line_wait_on_bit_lock(void *, int, int (*)(void *), unsigned));
  151. wait_queue_head_t *FASTCALL(bit_waitqueue(void *, int));
  152.  
  153. #define wake_up(x)            __wake_up(x, TASK_UNINTERRUPTIBLE | TASK_INTERRUPTIBLE, 1, NULL)
  154. #define wake_up_nr(x, nr)        __wake_up(x, TASK_UNINTERRUPTIBLE | TASK_INTERRUPTIBLE, nr, NULL)
  155. #define wake_up_all(x)            __wake_up(x, TASK_UNINTERRUPTIBLE | TASK_INTERRUPTIBLE, 0, NULL)
  156. #define wake_up_interruptible(x)    __wake_up(x, TASK_INTERRUPTIBLE, 1, NULL)
  157. #define wake_up_interruptible_nr(x, nr)    __wake_up(x, TASK_INTERRUPTIBLE, nr, NULL)
  158. #define wake_up_interruptible_all(x)    __wake_up(x, TASK_INTERRUPTIBLE, 0, NULL)
  159. #define    wake_up_locked(x)        __wake_up_locked((x), TASK_UNINTERRUPTIBLE | TASK_INTERRUPTIBLE)
  160. #define wake_up_interruptible_sync(x)   __wake_up_sync((x),TASK_INTERRUPTIBLE, 1)
  161.  
  162. #define __wait_event(wq, condition)                     \
  163. do {                                    \
  164.     DEFINE_WAIT(__wait);                        \
  165.                                     \
  166.     for (;;) {                            \
  167.         prepare_to_wait(&wq, &__wait, TASK_UNINTERRUPTIBLE);    \
  168.         if (condition)                        \
  169.             break;                        \
  170.         schedule();                        \
  171.     }                                \
  172.     finish_wait(&wq, &__wait);                    \
  173. } while (0)
  174.  
  175. #define wait_event(wq, condition)                     \
  176. do {                                    \
  177.     if (condition)                             \
  178.         break;                            \
  179.     __wait_event(wq, condition);                    \
  180. } while (0)
  181.  
  182. #define __wait_event_timeout(wq, condition, ret)            \
  183. do {                                    \
  184.     DEFINE_WAIT(__wait);                        \
  185.                                     \
  186.     for (;;) {                            \
  187.         prepare_to_wait(&wq, &__wait, TASK_UNINTERRUPTIBLE);    \
  188.         if (condition)                        \
  189.             break;                        \
  190.         ret = schedule_timeout(ret);                \
  191.         if (!ret)                        \
  192.             break;                        \
  193.     }                                \
  194.     finish_wait(&wq, &__wait);                    \
  195. } while (0)
  196.  
  197. #define wait_event_timeout(wq, condition, timeout)            \
  198. ({                                    \
  199.     long __ret = timeout;                        \
  200.     if (!(condition))                         \
  201.         __wait_event_timeout(wq, condition, __ret);        \
  202.     __ret;                                \
  203. })
  204.  
  205. #define __wait_event_interruptible(wq, condition, ret)            \
  206. do {                                    \
  207.     DEFINE_WAIT(__wait);                        \
  208.                                     \
  209.     for (;;) {                            \
  210.         prepare_to_wait(&wq, &__wait, TASK_INTERRUPTIBLE);    \
  211.         if (condition)                        \
  212.             break;                        \
  213.         if (!signal_pending(current)) {                \
  214.             schedule();                    \
  215.             continue;                    \
  216.         }                            \
  217.         ret = -ERESTARTSYS;                    \
  218.         break;                            \
  219.     }                                \
  220.     finish_wait(&wq, &__wait);                    \
  221. } while (0)
  222.  
  223. #define wait_event_interruptible(wq, condition)                \
  224. ({                                    \
  225.     int __ret = 0;                            \
  226.     if (!(condition))                        \
  227.         __wait_event_interruptible(wq, condition, __ret);    \
  228.     __ret;                                \
  229. })
  230.  
  231. #define __wait_event_interruptible_timeout(wq, condition, ret)        \
  232. do {                                    \
  233.     DEFINE_WAIT(__wait);                        \
  234.                                     \
  235.     for (;;) {                            \
  236.         prepare_to_wait(&wq, &__wait, TASK_INTERRUPTIBLE);    \
  237.         if (condition)                        \
  238.             break;                        \
  239.         if (!signal_pending(current)) {                \
  240.             ret = schedule_timeout(ret);            \
  241.             if (!ret)                    \
  242.                 break;                    \
  243.             continue;                    \
  244.         }                            \
  245.         ret = -ERESTARTSYS;                    \
  246.         break;                            \
  247.     }                                \
  248.     finish_wait(&wq, &__wait);                    \
  249. } while (0)
  250.  
  251. #define wait_event_interruptible_timeout(wq, condition, timeout)    \
  252. ({                                    \
  253.     long __ret = timeout;                        \
  254.     if (!(condition))                        \
  255.         __wait_event_interruptible_timeout(wq, condition, __ret); \
  256.     __ret;                                \
  257. })
  258.  
  259. #define __wait_event_interruptible_exclusive(wq, condition, ret)    \
  260. do {                                    \
  261.     DEFINE_WAIT(__wait);                        \
  262.                                     \
  263.     for (;;) {                            \
  264.         prepare_to_wait_exclusive(&wq, &__wait,            \
  265.                     TASK_INTERRUPTIBLE);        \
  266.         if (condition)                        \
  267.             break;                        \
  268.         if (!signal_pending(current)) {                \
  269.             schedule();                    \
  270.             continue;                    \
  271.         }                            \
  272.         ret = -ERESTARTSYS;                    \
  273.         break;                            \
  274.     }                                \
  275.     finish_wait(&wq, &__wait);                    \
  276. } while (0)
  277.  
  278. #define wait_event_interruptible_exclusive(wq, condition)        \
  279. ({                                    \
  280.     int __ret = 0;                            \
  281.     if (!(condition))                        \
  282.         __wait_event_interruptible_exclusive(wq, condition, __ret);\
  283.     __ret;                                \
  284. })
  285.  
  286. #ifdef __KERNEL__
  287.  
  288. /*
  289.  * Must be called with the spinlock in the wait_queue_head_t held.
  290.  */
  291. static inline void add_wait_queue_exclusive_locked(wait_queue_head_t *q,
  292.                            wait_queue_t * wait)
  293. {
  294.     wait->flags |= WQ_FLAG_EXCLUSIVE;
  295.     __add_wait_queue_tail(q,  wait);
  296. }
  297.  
  298. /*
  299.  * Must be called with the spinlock in the wait_queue_head_t held.
  300.  */
  301. static inline void remove_wait_queue_locked(wait_queue_head_t *q,
  302.                         wait_queue_t * wait)
  303. {
  304.     __remove_wait_queue(q,  wait);
  305. }
  306.  
  307. #endif /* __KERNEL__ */
  308.  
  309. /*
  310.  * These are the old interfaces to sleep waiting for an event.
  311.  * They are racy.  DO NOT use them, use the wait_event* interfaces above.  
  312.  * We plan to remove these interfaces during 2.7.
  313.  */
  314. extern void FASTCALL(sleep_on(wait_queue_head_t *q));
  315. extern long FASTCALL(sleep_on_timeout(wait_queue_head_t *q,
  316.                       signed long timeout));
  317. extern void FASTCALL(interruptible_sleep_on(wait_queue_head_t *q));
  318. extern long FASTCALL(interruptible_sleep_on_timeout(wait_queue_head_t *q,
  319.                             signed long timeout));
  320.  
  321. /*
  322.  * Waitqueues which are removed from the waitqueue_head at wakeup time
  323.  */
  324. void FASTCALL(prepare_to_wait(wait_queue_head_t *q,
  325.                 wait_queue_t *wait, int state));
  326. void FASTCALL(prepare_to_wait_exclusive(wait_queue_head_t *q,
  327.                 wait_queue_t *wait, int state));
  328. void FASTCALL(finish_wait(wait_queue_head_t *q, wait_queue_t *wait));
  329. int autoremove_wake_function(wait_queue_t *wait, unsigned mode, int sync, void *key);
  330. int wake_bit_function(wait_queue_t *wait, unsigned mode, int sync, void *key);
  331.  
  332. #define DEFINE_WAIT(name)                        \
  333.     wait_queue_t name = {                        \
  334.         .task        = current,                \
  335.         .func        = autoremove_wake_function,        \
  336.         .task_list    = {    .next = &(name).task_list,    \
  337.                     .prev = &(name).task_list,    \
  338.                 },                    \
  339.     }
  340.  
  341. #define DEFINE_WAIT_BIT(name, word, bit)                \
  342.     struct wait_bit_queue name = {                    \
  343.         .key = __WAIT_BIT_KEY_INITIALIZER(word, bit),        \
  344.         .wait    = {                        \
  345.             .task        = current,            \
  346.             .func        = wake_bit_function,        \
  347.             .task_list    =                \
  348.                 LIST_HEAD_INIT((name).wait.task_list),    \
  349.         },                            \
  350.     }
  351.  
  352. #define init_wait(wait)                            \
  353.     do {                                \
  354.         (wait)->task = current;                    \
  355.         (wait)->func = autoremove_wake_function;        \
  356.         INIT_LIST_HEAD(&(wait)->task_list);            \
  357.     } while (0)
  358.  
  359. /**
  360.  * wait_on_bit - wait for a bit to be cleared
  361.  * @word: the word being waited on, a kernel virtual address
  362.  * @bit: the bit of the word being waited on
  363.  * @action: the function used to sleep, which may take special actions
  364.  * @mode: the task state to sleep in
  365.  *
  366.  * There is a standard hashed waitqueue table for generic use. This
  367.  * is the part of the hashtable's accessor API that waits on a bit.
  368.  * For instance, if one were to have waiters on a bitflag, one would
  369.  * call wait_on_bit() in threads waiting for the bit to clear.
  370.  * One uses wait_on_bit() where one is waiting for the bit to clear,
  371.  * but has no intention of setting it.
  372.  */
  373. static inline int wait_on_bit(void *word, int bit,
  374.                 int (*action)(void *), unsigned mode)
  375. {
  376.     if (!test_bit(bit, word))
  377.         return 0;
  378.     return out_of_line_wait_on_bit(word, bit, action, mode);
  379. }
  380.  
  381. /**
  382.  * wait_on_bit_lock - wait for a bit to be cleared, when wanting to set it
  383.  * @word: the word being waited on, a kernel virtual address
  384.  * @bit: the bit of the word being waited on
  385.  * @action: the function used to sleep, which may take special actions
  386.  * @mode: the task state to sleep in
  387.  *
  388.  * There is a standard hashed waitqueue table for generic use. This
  389.  * is the part of the hashtable's accessor API that waits on a bit
  390.  * when one intends to set it, for instance, trying to lock bitflags.
  391.  * For instance, if one were to have waiters trying to set bitflag
  392.  * and waiting for it to clear before setting it, one would call
  393.  * wait_on_bit() in threads waiting to be able to set the bit.
  394.  * One uses wait_on_bit_lock() where one is waiting for the bit to
  395.  * clear with the intention of setting it, and when done, clearing it.
  396.  */
  397. static inline int wait_on_bit_lock(void *word, int bit,
  398.                 int (*action)(void *), unsigned mode)
  399. {
  400.     if (!test_and_set_bit(bit, word))
  401.         return 0;
  402.     return out_of_line_wait_on_bit_lock(word, bit, action, mode);
  403. }
  404.     
  405. #endif
  406.